xm,xend: Make cpus parameter available
authorKeir Fraser <keir.fraser@citrix.com>
Wed, 9 Sep 2009 14:33:30 +0000 (15:33 +0100)
committerKeir Fraser <keir.fraser@citrix.com>
Wed, 9 Sep 2009 14:33:30 +0000 (15:33 +0100)
When I started a VM by using xm create command, cpus parameter in VM
configuration files was ignored.  The problem occurred only when I
used XenAPI. This patch makes the parameter available.

Signed-off-by: Masaki Kanno <kanno.masaki@jp.fujitsu.com>
tools/python/xen/xend/XendConfig.py
tools/python/xen/xend/XendDomainInfo.py
tools/python/xen/xm/xenapi_create.py

index 06291a2ecf3bd34e2bfe6f3708526d367c001104..d5cd17cf1b9c3f4e8e857378ea50de7c4fae0121 100644 (file)
@@ -547,7 +547,28 @@ class XendConfig(dict):
 
         if 'handle' in dominfo:
             self['uuid'] = uuid.toString(dominfo['handle'])
-            
+
+    def _convert_cpus_to_list(self, s):
+        # Convert the following string to list of ints.
+        # The string supports a list of ranges (0-3),
+        # seperated by commas, and negation (^1).  
+        # Precedence is settled by order of the string:
+        #    "0-3,^1"   -> [0,2,3]
+        #    "0-3,^1,1" -> [0,1,2,3]
+        l = []
+        for c in s.split(','):
+            if c.find('-') != -1:
+                (x, y) = c.split('-')
+                for i in range(int(x), int(y)+1):
+                    l.append(int(i))
+            else:
+                # remove this element from the list 
+                if c[0] == '^':
+                    l = [x for x in l if x != int(c[1:])]
+                else:
+                    l.append(int(c))
+        return l
+
     def parse_cpuid(self, cfg, field):
        def int2bin(n, count=32):
            return "".join([str((n >> y) & 1) for y in range(count-1, -1, -1)])
@@ -692,27 +713,6 @@ class XendConfig(dict):
         # Convert 'cpus' to list of list of ints
         cpus_list = []
         if 'cpus' in cfg:
-            # Convert the following string to list of ints.
-            # The string supports a list of ranges (0-3),
-            # seperated by commas, and negation (^1).  
-            # Precedence is settled by order of the string:
-            #    "0-3,^1"      -> [0,2,3]
-            #    "0-3,^1,1"    -> [0,1,2,3]
-            def cnv(s):
-                l = []
-                for c in s.split(','):
-                    if c.find('-') != -1:
-                        (x, y) = c.split('-')
-                        for i in range(int(x), int(y)+1):
-                            l.append(int(i))
-                    else:
-                        # remove this element from the list 
-                        if c[0] == '^':
-                            l = [x for x in l if x != int(c[1:])]
-                        else:
-                            l.append(int(c))
-                return l
-            
             if type(cfg['cpus']) == list:
                 if len(cfg['cpus']) > 0 and type(cfg['cpus'][0]) == list:
                     # If sxp_cfg was created from config.sxp,
@@ -736,7 +736,7 @@ class XendConfig(dict):
                     #    ["0-3,^1","1-4,^2"] -> [[0,2,3],[1,3,4]]
                     try:
                         for c in cfg['cpus']:
-                            cpus = cnv(c)
+                            cpus = self._convert_cpus_to_list(c)
                             cpus_list.append(cpus)
                     except ValueError, e:
                         raise XendConfigError('cpus = %s: %s' % (cfg['cpus'], e))
@@ -752,7 +752,7 @@ class XendConfig(dict):
                 #    "1"      -> [[1],[1]]
                 #    "0-3,^1" -> [[0,2,3],[0,2,3]]
                 try:
-                    cpus = cnv(cfg['cpus'])
+                    cpus = self._convert_cpus_to_list(cfg['cpus'])
                     for v in range(0, cfg['vcpus']):
                         cpus_list.append(cpus)
                 except ValueError, e:
@@ -1020,7 +1020,13 @@ class XendConfig(dict):
                 
         self['vcpus_params']['weight'] = \
             int(self['vcpus_params'].get('weight', 256))
-        self['vcpus_params']['cap'] = int(self['vcpus_params'].get('cap', 0))
+        self['vcpus_params']['cap'] = \
+            int(self['vcpus_params'].get('cap', 0))
+
+        for key, val in self['vcpus_params'].items():
+            if key.startswith('cpumap'):
+                self['vcpus_params'][key] = \
+                    ','.join(map(str, self._convert_cpus_to_list(val)))
 
     def cpuid_to_sxp(self, sxpr, field):
         regs_list = []
index cf9611e212c3bc36f119d8e6da24bc9551011119..4cc204b18843946516d98ceb9f136f3c86dfdd31 100644 (file)
@@ -2538,7 +2538,19 @@ class XendDomainInfo:
                         return True
             return False
 
-        if has_cpus():
+        def has_cpumap():
+            if self.info.has_key('vcpus_params'):
+                for k, v in self.info['vcpus_params'].items():
+                    if k.startswith('cpumap'):
+                        return True
+            return False
+
+        if has_cpumap():
+            for v in range(0, self.info['VCPUs_max']):
+                if self.info['vcpus_params'].has_key('cpumap%i' % v):
+                    cpumask = map(int, self.info['vcpus_params']['cpumap%i' % v].split(','))
+                    xc.vcpu_setaffinity(self.domid, v, cpumask)
+        elif has_cpus():
             for v in range(0, self.info['VCPUs_max']):
                 if self.info['cpus'][v]:
                     xc.vcpu_setaffinity(self.domid, v, self.info['cpus'][v])
index cb7130bebcd8faaffdde13411edb66c231562346..27702635ae323d26bdfa0b4e2486fc3fbbfb15e8 100644 (file)
@@ -1094,6 +1094,23 @@ class sxp2xml:
             = str(get_child_by_name(config, "cpu_cap", 0))
         vcpu_params.append(vcpu_param)
 
+        cpus = get_child_by_name(config, "cpus", [])
+        if type(cpus) == list:
+            vcpu = 0
+            for cpu in cpus:
+                if cpu:
+                    vcpu_param = document.createElement("vcpu_param")
+                    vcpu_param.attributes["key"] = "cpumap%i" % vcpu
+                    vcpu_param.attributes["value"] = str(cpu)
+                    vcpu_params.append(vcpu_param)
+                vcpu = vcpu + 1
+        else:
+            for vcpu in range(0, int(get_child_by_name(config, "vcpus", 1))):
+                vcpu_param = document.createElement("vcpu_param")
+                vcpu_param.attributes["key"] = "cpumap%i" % vcpu
+                vcpu_param.attributes["value"] = str(cpus)
+                vcpu_params.append(vcpu_param)
+
         return vcpu_params
     
     _eths = -1